import BNode from "./BNode";
import BTreeTools from "../BTreeTools";

const {ccclass, property} = cc._decorator;

@ccclass
export default class BTree extends cc.Component {

    /**
     * 行为树是否停止
     * @type {boolean}
     */
    private isStop:boolean = false;

    onLoad(): void {
        // cc.loader.loadRes("tree_data/test", cc.TextAsset, (err, content) => {
        //     this.readJson(content);
        // });
        // var JS = cc.js;
        // let Constructor:any = JS.getClassByName("BNodeLog");
        // let a:any = new Constructor();
    }

    update(dt):void{
        this.run();
    }
    private m_Root: BNode = null;
    private nodeDataArray: Array<any>;
    public setTreeJsonPath(path:string):void{
        cc.loader.loadRes(path, cc.TextAsset, (err, content) => {
            if(err){
                cc.error("加载行为树数据出错：" + path);
            }else{
                this.readJson(content);
            }
        });
    }

    private readJson(jsonData: any): void {
        // let treeData: any = JSON.parse(jsonData);
        let treeData: any = jsonData;
        this.nodeDataArray = treeData["nodeDataArray"];
        let rootNode = this.getNodeByType("Root");
        this.initTreeData(rootNode);
        this.m_Root = BTreeTools.instance.getNewBNode(rootNode["type"]);
        this.m_Root.bTree = this;
        this.m_Root.readJson(rootNode);
    }

    /**
     * 初始化数据排序等
     * @param rootNodeData
     */
    private initTreeData(rootNodeData: any) {
        let sunNodeArray = this.getNodesByParentKey(rootNodeData["key"]);
        if(sunNodeArray.length<=0){
            return;
        }
        sunNodeArray = sunNodeArray.sort(this.orderFromTopToDown);
        rootNodeData["childs"] = sunNodeArray;
        for (let i = 0; i < sunNodeArray.length; i++) {
            this.initTreeData(sunNodeArray[i]);
        }
    }
    public stop():void{
        this.isStop = true;
    }
    private run(): void {
        if(this.m_Root && !this.isStop){
            this.m_Root.runNode();
        }
    }

    private getNodeByType(type): any {
        for (let node of this.nodeDataArray) {
            if (node.type == type) {
                return node;
            }
        }
    }

    private getNodesByParentKey(key): Array<any> {
        let nodes = [];
        for (let node of this.nodeDataArray) {
            if (node.parent !== undefined && node.parent == key) {
                nodes.push(node);
            }
        }
        return nodes;
    }

    private orderFromTopToDown(a, b): number {
        let ax = a.loc.split(" ")[0];
        let bx = b.loc.split(" ")[0];
        //Editor.log(ay,by,(ay - by) | 0);
        return (ax - bx) | 0;
    }
    private variableMap:Map<string,any> = new Map<string, any>();

    /**
     * 获取共享变量
     * @param {string} variableName
     * @returns {T}
     */
    public getVariable<T>(variableName:string):T{
        return this.variableMap.get(variableName);
    }

    /**
     * 设置共享变量
     * @param {string} variableName
     * @param value
     */
    public setVariable(variableName:string,value:any):void{
        this.variableMap.set(variableName,value);
    }

    /**
     * 删除共享变量
     * @param {string} variableName
     */
    public deleteVariable(variableName:string):void{
        this.variableMap.delete(variableName);
    }

}
